package design_pattern.WorkerThreadMode;

import java.util.Arrays;

/**
 * @Author: 蔡翔
 * @Date: 2019/11/19 10:20
 * @Version 1.0
 */
public class Channel {
    private final static int MAX_REQUEST = 100;
    private final Request[] requestQueue;

    private int head;
    private int tail;
    private int count;
    private final WorkThread[] workerPool;

    public Channel(int workers) {
        this.requestQueue = new Request[MAX_REQUEST];
        this.head = 0;
        this.tail = 0;
        this.count = 0;
        this.workerPool = new WorkThread[workers];
        this.init();
    }

    private void init() {
        for(int i=0;i<workerPool.length;i++){
            workerPool[i] = new WorkThread("Worker-"+i,this);
        }
    }

    //流水线上 每个点都起来了。
    public void startWorker(){
        Arrays.asList(workerPool).forEach(i->{
            i.start();
        });
    }

    public synchronized void put(Request request){
        //如果流水线上的工人太多了，那只能先等着了。
        while (count>=requestQueue.length){
            try {
                this.wait();
            }catch (Exception e){

            }
        }

        this.requestQueue[tail] = request;
        this.tail = (this.tail+1)%requestQueue.length;
        this.count++;
        this.notifyAll();

    }

    public synchronized Request take(){
        while (count<=0){
            try {
                this.wait();
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
        Request request = this.requestQueue[head];
        this.head = (this.head+1)%requestQueue.length;
        this.count--;
        this.notifyAll();
        return request;
    }

}
